package com.jtx.miaoah2.Service.Impl;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.jtx.miaoah2.Common.BaseResponse;
import com.jtx.miaoah2.Common.CustomException;
import com.jtx.miaoah2.Common.RedisConstants;
import com.jtx.miaoah2.Mapper.SkUserMapper;
import com.jtx.miaoah2.Model.user.DO.SkUser;
import com.jtx.miaoah2.Model.user.DTO.SkUserDto;
import com.jtx.miaoah2.Service.SkUserService;
import com.jtx.miaoah2.Utils.JwtUtils;
import com.jtx.miaoah2.Utils.PasswordUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.logging.log4j.util.Strings;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.io.UnsupportedEncodingException;
import java.security.NoSuchAlgorithmException;
import java.util.Date;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @author 季台星
 * @Date 2023 07 23 14 03
 */
@Service
@Transactional
@Slf4j
public class SkUserServiceImpl extends ServiceImpl<SkUserMapper,SkUser> implements SkUserService {
    @Autowired
    private StringRedisTemplate stringRedisTemplate;
    @Autowired
    private SkUserMapper skUserMapper;
    @Override
    public BaseResponse login(SkUserDto userDto) {
        String nickName = userDto.getNickName();
        String password = userDto.getPassword();
        //1.校验参数
        if (Strings.isBlank(nickName) || Strings.isBlank(password)){
            throw new CustomException("账号或密码不得为空");
        }
        //判断数据库中是否有此用户
        SkUser skUserFromDB = skUserMapper.selectOne(new LambdaQueryWrapper<SkUser>().eq(SkUser::getNickName, nickName));
        if (null == skUserFromDB){
            throw new CustomException(403,"账号未注册，请先前往注册");
        }
        //比对账号密码是否一致
        boolean flag = PasswordUtil.validPassword(password, skUserFromDB.getSalt(), skUserFromDB.getPassword());
        if (!flag){
            throw new CustomException(405, "密码错误");
        }
        //使用UserId生成Token信息
        String jwt = JwtUtils.createJWT(skUserFromDB.getId().toString());
        //redis以键存储用户信息
        String userInfo = JSON.toJSONString(skUserFromDB);
        stringRedisTemplate.opsForValue().set(RedisConstants.USER_INFO + skUserFromDB.getId(),userInfo,2, TimeUnit.HOURS);
        return BaseResponse.success("登入成功",jwt);
    }

    @Override
    public BaseResponse register(SkUserDto skUserDto) {
        String nickName = skUserDto.getNickName();
        String password = skUserDto.getPassword();
        if (Strings.isBlank(nickName) || Strings.isBlank(password)){
            throw new CustomException("账号密码不得为空");
        }
        //判断数据库中是否已经有数据
        //使用布隆过滤器也可以
        List<SkUser> skUserListFromDB = null;
        skUserListFromDB = skUserMapper.selectList(new LambdaQueryWrapper<SkUser>().eq(SkUser::getNickName, nickName));
        if (!skUserListFromDB.isEmpty()){
            throw new CustomException("用户已经存在");
        }
        SkUser skUserToDB = new SkUser();
        BeanUtils.copyProperties(skUserDto,skUserToDB);
        //将密码进行加盐
        skUserToDB.setSalt(PasswordUtil.getSalt());
        skUserToDB.setPassword(PasswordUtil.getMD5Encryption(skUserToDB.getPassword(), skUserToDB.getSalt()));
        skUserToDB.setRegisterDate(new Date());
        try {
            int insert = skUserMapper.insert(skUserToDB);
            if (insert <= 0){
                throw new CustomException("注册用户储存到DB中出现问题");
            }
        } catch (Exception e) {
            log.info("插入数据库发送异常,异常原因为：{}", e.getMessage());
            throw new CustomException("注册用户储存到DB中出现问题");
        }
        return BaseResponse.success(skUserToDB);
    }
}
